#import "RNSearch.h"
#import "SearchSubHeader.h"
#import "RNConstants.h"

static RNSearch *sharedSearch = nil;

@interface RNSearch (SearchPrivateMethods)
-(void)updateDisplayHeaders_;
@end
    
    
@implementation RNSearch

@synthesize searchString = searchString_;
@synthesize applicationSearchType = applicationSearchType_;
@synthesize subheaders = subheaders_;
@synthesize displayHeaders = displayHeaders_;
@synthesize itemsController = itemsController_;
@synthesize categoriesController = categoriesController_;
@synthesize aislesController = aislesController_;

+(RNSearch *)sharedSearch {
    if (!sharedSearch)
        sharedSearch = [[RNSearch alloc] init];
    return sharedSearch;
}

-(id)init {
    if (!(self = [super init]))
        return nil;

    [NSBundle loadNibNamed:@"ApplicationSearchControllers" owner:self];
    NSMutableDictionary *subheaderDictionary = [NSMutableDictionary dictionaryWithCapacity:3];
    SearchSubHeader *subheader = [[SearchSubHeader alloc] initWithController:[self itemsController]];   
    [subheader setFilterPredicateTemplate:[NSPredicate predicateWithFormat:@"title CONTAINS[cd] $FILTER_STRING"]];
    [subheader setDisplayIndex:0];
    [subheaderDictionary setObject:subheader forKey:[NSNumber numberWithInteger:RNSearchTypeItem]];
    [[subheader controller] addObserver:self forKeyPath:@"arrangedObjects" options:NSKeyValueObservingOptionNew context:NULL];

    subheader = [[SearchSubHeader alloc] initWithController:[self categoriesController]];    
    [subheader setFilterPredicateTemplate:[NSPredicate predicateWithFormat:@"title CONTAINS[cd] $FILTER_STRING"]];
    [subheader setDisplayIndex:1];
    [subheaderDictionary setObject:subheader forKey:[NSNumber numberWithInteger:RNSearchTypeCategory]];
    [[subheader controller] addObserver:self forKeyPath:@"arrangedObjects" options:NSKeyValueObservingOptionNew context:NULL];

    subheader = [[SearchSubHeader alloc] initWithController:[self aislesController]];    
    [subheader setFilterPredicateTemplate:[NSPredicate predicateWithFormat:@"title CONTAINS[cd] $FILTER_STRING"]];
    [subheader setDisplayIndex:2];
    [subheaderDictionary setObject:subheader forKey:[NSNumber numberWithInteger:RNSearchTypeAisle]];
    [[subheader controller] addObserver:self forKeyPath:@"arrangedObjects" options:NSKeyValueObservingOptionNew context:NULL];

    [self setSubheaders:subheaderDictionary];
    [self setApplicationSearchType:RNSearchTypeAll];
    [self updateDisplayHeaders_];
    
    return self;
}

- (void)observeValueForKeyPath:(NSString *)keyPath ofObject:(id)object change:(NSDictionary *)change context:(void *)context {
    [self updateDisplayHeaders_];
}

-(NSString *)title {
    return @"Search";
}

-(void)setSearchString:(NSString *)theString {
    searchString_ = [theString copy];
    if (!searchString_)
        return;
    for (NSNumber *key in [self subheaders]) {
        SearchSubHeader *header = [[self subheaders] objectForKey:key];
        [header updateFilterWithString:theString];
    }
}

-(void)setApplicationSearchType:(RNSearchType)type {
    applicationSearchType_ = type;
    [self updateDisplayHeaders_];
}

-(void)updateDisplayHeaders_ {
    NSMutableSet *headers = [NSMutableSet set];
    if ([self applicationSearchType] == RNSearchTypeAll) {
        for (NSNumber *key in [self subheaders]) {
            SearchSubHeader *header = [[self subheaders] objectForKey:key];
            if ([[[header controller] arrangedObjects] count] > 0)
                [headers addObject:header];
        }
    }
    else {
        SearchSubHeader *header = [[self subheaders] objectForKey:[NSNumber numberWithInteger:[self applicationSearchType]]];
        if ([[[header controller] arrangedObjects] count] > 0)
            [headers addObject:header];
    }
    [self setDisplayHeaders:headers];
}

// TODO: IS THIS METHOD NECESSARY?
-(NSArray *)children {
    return nil;
}

-(id)parent {
    return nil;
}

@end
